home *** CD-ROM | disk | FTP | other *** search
/ Garbo / Garbo.cdr / mac / source / music4c.sit / Music4C Folder / Sources Folder / ugenlib.c < prev    next >
Text File  |  1990-06-22  |  49KB  |  2,079 lines

  1. /*
  2. * ⌐ Graeme Gerrard 1990
  3. * Faculty of Music, University of Melbourne
  4. * Parkville Victoria 3052 Australia.
  5. *
  6. * ARPANET: grae@murdu.ucs.unimelb.edu.au
  7. * telephone: (613) 344 4127, Fax: (613) 344 5346
  8. */
  9.  
  10.  
  11. /* WARNING: Beware of (int) casts for truncation. Remember, THINK C ints
  12. are only 16 bits!. This may cause trouble when truncating large numbers,
  13. like sample numbers!
  14. */
  15.  
  16. #include    "Music4C.h"
  17. #include    "orch.h"
  18. #include    <math.h>
  19. #include    <unix.h>
  20. #include    "Music4C_Prototype.h"
  21. #include    "ErrorAlert.h"
  22. #include    "SDtype.h"
  23.  
  24.  
  25. extern    int loc;
  26. extern    double    *out;
  27. extern    int    nchnls;
  28. extern    double    *F[MAXFUNCS];
  29. extern    double    srate;
  30. extern    OSErr    theErr;
  31. extern    Str255    theMess1;
  32.  
  33.  
  34.  
  35.  
  36.  
  37. double add8vepc(p1, p2)
  38.     double    p1, p2;
  39. {
  40.     double    c1, c2, temp, nclass;
  41.     int pos, oct1, oct2, octnxt;
  42.  
  43.     /* adds together 2 8ve.pc pitches */
  44.  
  45.     oct1 = (int)p1;
  46.     c1 = p1 - oct1;
  47.     oct2 = (int)p2;
  48.     if ( oct2 < 0 ) {
  49.         pos = -oct2;
  50.         c2 = p2 + (double)pos;
  51.     }
  52.     else
  53.         c2 = p2 - (double)oct2;
  54.     temp = (c1+c2) * 100.0;    /* shift for roundoff/truncation */
  55.     octnxt = (int)(temp/12.0) + oct1 + oct2;
  56.     if ( temp < 0.0 ) {
  57.         octnxt -= 1;
  58.         nclass = (12.0 + (int)temp % 12) / 100.0;
  59.     }
  60.     else {
  61.         nclass =  ((int)temp % 12) / 100.0;
  62.     }
  63.     return(octnxt+nclass);
  64. }
  65.  
  66. void en3set( ta, ts, td, a )
  67.  
  68.     double    ta, ts, td, *a;
  69. {
  70.     register    n;
  71.     register    double    fac = 128.0 / srate;
  72.     register    double    st = 1.0 / srate;
  73.     register    double t[3];
  74.  
  75.     *t = ta;
  76.     *(t+1) = ts;
  77.     *(t+2) = td;
  78.  
  79.     for ( n = 0; n < 3; n++ ) {
  80.         if ( *(t+n) <= st ) *(t+n) = st;
  81.         *(a+n) = fac / *(t+n);
  82.     }
  83.     *(a+3) = 1.0 - *(a);
  84. }    /* en3set */
  85.  
  86. double envel3(amp, fno, a)
  87.     double    amp, *a;
  88.     int    fno;
  89. {
  90.     register k;
  91.     if ( *(a+3) < 128.0) {
  92.         *(a+3) += *(a);
  93.         if (*(a+3) > 128.0) *(a+3) = 128.0;
  94.     }
  95.     else if (*(a+3) < 256.0) {
  96.         *(a+3) += *(a+1);
  97.         if (*(a+3) > 256.0) *(a+3) = 256.0;
  98.     }
  99.     else if (*(a+3) < 384.0) {
  100.         *(a+3) += *(a+2);
  101.         if (*(a+3) > 384.0) *(a+3) = 384.0;
  102.     }
  103.     else
  104.         *(a+3) = 384.0;
  105.     k = (int)(*(a+3) + 0.5); /* round to add 1 for length in F[0] */
  106.  
  107.     return(amp * *(F[fno] + k));
  108. }
  109.  
  110.  
  111. double envel3I(amp, fno, a)
  112.     double    amp, *a;
  113.     int    fno;
  114. {
  115.     /* interpolating version of envel3 */
  116.     register  k, l;
  117.     double    diff;
  118.     if ( *(a+3) < 128.0) {
  119.         *(a+3) += *(a);
  120.         if (*(a+3) > 128.0) *(a+3) = 128.0;
  121.     }
  122.     else if (*(a+3) < 256.0) {
  123.         *(a+3) += *(a+1);
  124.         if (*(a+3) > 256.0) *(a+3) = 256.0;
  125.     }
  126.     else if (*(a+3) < 384.0) {
  127.         *(a+3) += *(a+2);
  128.         if (*(a+3) > 384.0) *(a+3) = 384.0;
  129.     }
  130.     else
  131.         *(a+3) = 384.0;
  132.     
  133.     if ( *(a+3) >= 384 )
  134.         return(amp * *(F[fno] + 384));
  135.     else {
  136.         k = *(a+3);
  137.         l = k+1;
  138.         diff = *(a+3) - (int)*(a+3);
  139.         return(amp * (*(F[fno] + k) + ((*(F[fno]+l)-*(F[fno]+k)) * diff)) );
  140.     }
  141. }
  142.  
  143.  
  144. void adsrset( att, dec, sus, rel, a )
  145.  
  146.     double    att, dec, sus, rel, *a;
  147. {
  148.     register         n;
  149.     register    double    fac = 128.0 / srate;
  150.     register    double    st = 1.0 / srate;
  151.     register    double t[4];
  152.  
  153.     *t = att;
  154.     *(t+1) = dec;
  155.     *(t+2) = sus;
  156.     *(t+3) = rel;
  157.  
  158.     for ( n = 0; n < 4; n++ ) {
  159.         if ( *(t+n) <= st ) *(t+n) = st;
  160.         *(a+n) = fac / *(t+n);
  161.     }
  162.     *(a+4) = 1.0 - *(a);
  163. }    /* adsrset */
  164.  
  165.  
  166.  
  167. double adsr(amp, fno, a)
  168.     double    amp, *a;
  169.     int    fno;
  170. {
  171.     register  k;
  172.     if ( *(a+4) < 128.0) {
  173.         *(a+4) += *(a);
  174.         if (*(a+4) > 128.0) *(a+4) = 128.0;
  175.     }
  176.     else if (*(a+4) < 256.0) {
  177.         *(a+4) += *(a+1);
  178.         if (*(a+4) > 256.0) *(a+4) = 256.0;
  179.     }
  180.     else if (*(a+4) < 384.0) {
  181.         *(a+4) += *(a+2);
  182.         if (*(a+4) > 384.0) *(a+4) = 384.0;
  183.     }
  184.     else if (*(a+4) < 512.0) {
  185.         *(a+4) += *(a+3);
  186.         if (*(a+4) > 512.0) *(a+4) = 512.0;
  187.     }
  188.     else
  189.         *(a+4) = 512.0;
  190.         
  191.     k = (int)(*(a+4) + 0.5); /* round to add 1 for length in F[0] */
  192.  
  193.     return(amp * *(F[fno] + k));
  194. }
  195.     
  196.  
  197. void blnset( bw, xinit, a )
  198.     double    bw, xinit, *a;
  199. {
  200.     void    toneset();
  201.     /* bw = 10.0 usual */
  202.     toneset(bw, xinit, a);
  203.     toneset(bw, xinit, (a+3));
  204. }
  205.  
  206. void cmbset( xloopt, xinit, a )
  207.     double    xloopt, xinit, *a;
  208. {
  209.     register        n;
  210.     int    le;
  211.  
  212.     *(a) = 4.0 + (long)(xloopt * srate + 0.5);
  213.     *(a+1) = xloopt;
  214.     if ( xinit <= 0.0 ) {
  215.         le = *(a);
  216.         for ( n = 5; n < le; n++)
  217.             *(a+n) = 0.0;
  218.         *(a+2) = 0.0;
  219.         *(a+3) = 0.0;
  220.         *(a+4) = 4.0;
  221.     }
  222. }
  223.  
  224. void slpset(a, b, dur)
  225.     double *a, *b, dur;
  226. {
  227.     *b = ( *b - *a) * ( 1.0 / (dur * srate));
  228.     *a -= *b;
  229. }
  230.  
  231. double slope(a, b)
  232.     double    *a, *b;
  233. {
  234.     *a += *b;
  235.     return( *a );
  236. }
  237.  
  238. void toneset( hpoint, xinit, a )
  239.     double    hpoint, xinit, *a;
  240. {
  241.     register    double    twopi  = 8.0 * atan(1.0);
  242.     register    double b = 2.0 - cos(hpoint * twopi / srate);
  243.     *(a+1) = b - sqrt(b*b - 1.0);
  244.     *(a) = 1.0 - *(a+1);
  245.     if ( hpoint < 0.0 ) *(a+1) = -*(a+1);
  246.     if ( xinit <= 0.0) *(a+2) = 0.0;
  247. }
  248.  
  249. double tone(x, a )
  250.     double    x, *a;
  251. {
  252.     *(a+2) = (*(a) * x) + (*(a+1) * *(a+2));
  253.     return(*(a+2));
  254. }
  255.  
  256. void evpset(delay, rise, dur, decay, nf1, nf2, a )
  257.     double    delay, rise, dur, decay, *a;
  258.     int nf1, nf2;
  259. {
  260.  
  261.     *(a) = period(rise);
  262. /* old    *(a+1) = (srate * delay * *(a));*/
  263.     *(a+1) = -(srate * delay * *(a));
  264.     
  265.     *(a+2) = -(period(decay));
  266.     *(a+3) = (511.9999 + *(a+2)) - (srate * (dur-decay) * *(a+2));
  267.     *(a+4) = (*(F[nf1] + 512)) * (*(F[nf2] + 512));
  268. }
  269.  
  270. double envlp(amp, nf1, nf2, a )
  271.     double amp, *a;
  272.     int    nf1, nf2;
  273. {
  274.     register    double    x;
  275.     x = oscil1(amp, *(a), nf1, (a+1));
  276.     return( oscil1(x, *(a+2), nf2, (a+3)) / *(a+4));
  277. }
  278.  
  279. void expset(a, b, dur)
  280.     double    *a, *b, dur;
  281. {
  282.     *b = pow( *b / *a , 1.0 / (dur * srate));
  283.     *a /= *b;
  284. }
  285.  
  286. double expon(a, b)
  287.     double *a, *b;
  288. {
  289.     *a *= *b;
  290.     return( *a );
  291. }
  292.  
  293.  
  294. double formnt( rms, si, fno1, fno2, fno3, fno4, a)
  295.     double    rms, si, *a;
  296.     int    fno1, fno2, fno3, fno4;
  297. {
  298.  
  299.     register    double    coef, freq;
  300.     register  i, j, k;
  301.     double x, ss, z, t;
  302.     /* a[0] = overall phase */
  303.     /* a[1] = previous sum of squares */
  304.     /* a[2] = rescaling divisor */
  305.     
  306.     ss = 0.0;
  307.     if ( rms != 0.0 ) {
  308.         z = 0.0;
  309.         for ( i = 1; i <= 508; i += 3 ) {
  310.             freq = *(F[fno2]+i);
  311.             if ( freq == 0.0 )
  312.                 break;    /*goto L4;*/
  313.             j = (long)(freq * si * 2.0 + 1.5);
  314.             if ( j > 512)
  315.                 break;    /*goto L4;*/
  316.             coef = *(F[fno2]+i+1) * *(F[fno3]+j);
  317.             if ( fno4 <= 0)
  318.                 x = coef;
  319.             else
  320.                 x = coef / *(F[fno4]+j);
  321.             ss += (x * x );
  322.             k = ((long)((freq * *a) + *(F[fno2]+i+2)) % 512) + 1.0;
  323.             z += (coef * *(F[fno1]+k));
  324.         }
  325.     }
  326. L4:
  327.     *a += si;
  328.     while ( *a >= 65536.0 )
  329.         *a -= 65536.0;
  330.         
  331.     if ( ss == 0.0 )
  332.         return(0.0);
  333.         
  334.     if ( ss != *(a+1)) {
  335.         *(a+2) = sqrt(ss / 2.0);
  336.         *(a+1) = ss;
  337.     }
  338.     return( z * rms / *(a+2));
  339. }
  340.  
  341. void hf2set(fc, zet, a)
  342.     double    fc, zet, *a;
  343. {
  344.     register    double    pi = 4.0 * atan(1.0);
  345.     register    double    wcp = tan(pi * fc / srate);
  346.     register    double    wcp2 = wcp * wcp;
  347.     register    double    twzwcp = 2.0 * zet * wcp;
  348.  
  349.     *(a+4) = 1.0 / ( 1.0 + twzwcp + wcp2 );
  350.     *(a+5) = 2.0 * ( 1.0 - wcp2) * *(a+4);
  351.     *(a+6) = -( 1.0 - twzwcp + wcp2) * *(a+4);
  352. }
  353.  
  354. double hpf2( y, a )
  355.     double    y, *a;
  356. {
  357. /* 2nd order high pass filter,
  358. * digital recursion formula parameter assignments:
  359. * *a = y1, *(a+1) = y2, *(a+2) = z1, *(a+3) = z2, *(a+4) = p0,
  360. * *(a+5) = q1, *(a+6) = q2.
  361. */
  362.     register    double sig = *(a+4) * ( y-*a-*a+*(a+1))
  363.                         + *(a+5) * *(a+2) + *(a+6) * *(a+3);
  364.     *(a+1) = *a;
  365.     *a = y;
  366.     *(a+3) = *(a+2);
  367.     *(a+2) = sig;
  368.     return(sig);
  369. }
  370.  
  371. void linset(rise, dur, decay, a)
  372.     double    rise, dur, decay, *a;
  373. {
  374.     *(a+3) = 0.0;
  375.     if ( rise == 0.0 ) *(a) = 0.0;
  376.     else {
  377.         *(a) = (long) (rise * srate + 1.5);
  378.         *(a+4) = 1.0 / *(a);
  379.         *(a+6) = -*(a+4);
  380.     }
  381.  
  382.     if ( decay == 0.0 ) *(a+2) = 0.0;
  383.     else {
  384.         *(a+2) = (long)(decay * srate + 0.5);
  385.         *(a+5) = 1.0 / *(a+2);
  386.         *(a+7) = 1.0;
  387.     }
  388.     *(a+1) = (long)(dur * srate + 0.5);
  389.     *(a+2) = *(a+1) - *(a+2);
  390. }
  391.  
  392. double linens(amp, a)
  393.     double    amp, *a;
  394. {
  395.     *(a+3) += 1.0;
  396.     if ( *(a+3) <= *(a)) {
  397.         *(a+6) += *(a+4);
  398.         return( amp * *(a+6));
  399.     }
  400.     else if ( *(a+3) <= *(a+2))
  401.         return(amp);
  402.     else if ( *(a+3) > *(a+2)) {
  403.         *(a+7) -= *(a+5);
  404.         return(amp * *(a+7));
  405.     }
  406.     else
  407.         return(0.0);
  408. }
  409.  
  410.  
  411. double nonlin(amp, x, fno)
  412.     double    amp, x;
  413.     int    fno;
  414. {
  415.     register    double    frac;
  416.     register     k, l;
  417.     /* interpolating lookup of transfer function for non-linear distortion
  418.      (waveshaping) */
  419.     k = x + (int)(*(F[fno])/2.0) + 1;
  420.     if ( k > (int)*(F[fno] - 1) )
  421.         k = (int)*(F[fno]);
  422.     else if ( k < 1 )
  423.         k = 1;
  424.     l = k + 1;
  425.     frac = x - (int)x;
  426.     return( amp * ( *(F[fno]+k) + ( *(F[fno]+l) - *(F[fno]+k)) * frac));
  427. }
  428.  
  429. double oscil(amp, si, fno, phs)
  430.     double    amp, si, *phs;
  431.     int    fno;
  432. {
  433.     /* truncating digital oscillator, negative samp incs ok */
  434.     register    double sig = amp * *(F[fno] + ((int)(*phs+1.0)));
  435.     *phs += si;
  436.     while (*phs < 0.0) {
  437.         *phs += *(F[fno]);
  438.     }
  439.     while (*phs >= *(F[fno])) {
  440.         *phs -= *(F[fno]);
  441.     }
  442.     return( sig );
  443. }
  444.  
  445. double oscil1(amp, si, fno, phs)
  446.     double    amp, si, *phs;
  447.     int    fno;
  448. {
  449.     register    double sig;
  450. /* truncating function lookup, samples function once,
  451. *  holds last value if phs exceeds *(F[fno]) i.e. length of function */
  452.     if (*phs >= *(F[fno]))
  453.         sig = amp * *(F[fno] + (int)*(F[fno]));
  454.     else {
  455.         if (*phs <= 0.0 )
  456.             sig = amp * *(F[fno] + 1);
  457.         else
  458.             sig = amp * *(F[fno] + ((int)(*phs+1.0)));
  459.     }
  460.     *phs += si;
  461.     return(sig);
  462. }
  463.  
  464. double osci1(amp, si, fno, phs)
  465.     double    amp, si, *phs;
  466.     int    fno;
  467. {
  468.     register    double    sig, frac;
  469.     register  k, l;
  470. /* interpolating version of oscil1 */
  471.     if (*phs >= *(F[fno]))
  472.         sig = amp * *(F[fno] + (int)*(F[fno]));
  473.     else {
  474.         if (*phs <= 0.0 )
  475.             sig = amp * *(F[fno] + 1);
  476.         else {
  477.             k = *phs + 1.0;
  478.             l = k + 1;
  479.             frac = *phs - (int)*phs;
  480.             sig = amp * ( *(F[fno]+k) + ( *(F[fno]+l) - *(F[fno]+k)) * frac);
  481.         }
  482.         *phs += si;
  483.     }
  484.     return(sig);
  485. }
  486.  
  487.  
  488. double oscili(amp, si, fno, phs)
  489.     double    amp, si, *phs;
  490.     int    fno;
  491. {
  492.     /* interpolating digital oscillator, negative samp incs ok */
  493.     register    double    sig, frac;
  494.     register     k, l;
  495.     k = *phs + 1.0;
  496.     l = k % (int)(*(F[fno])) + 1;
  497.     frac = *phs - (int)*phs;
  498.     *phs += (si);
  499.     while (*phs < 0.0)
  500.         *phs += *(F[fno]);
  501.     while (*phs >= *(F[fno]))
  502.         *phs -= *(F[fno]);
  503.     sig = amp * ( *(F[fno]+k) + ( *(F[fno]+l) - *(F[fno]+k)) * frac);
  504.     return(sig);
  505. }
  506.  
  507. void rsnset(cf, bw, scl, xinit, a )
  508.     double    cf, bw, scl, xinit, *a;
  509. {
  510. /*
  511. * scl = 1.0 sets gain at 1.0 cf
  512. * scl = 2.0 sets gain at 1.0 on random input
  513. * scl = 0.0 means no scaling
  514. */
  515.     register    double    twopi = 8.0 * atan(1.0);
  516.     register    double    c;
  517.     if ( xinit <= 0.0 ) {
  518.         *(a+4) = 0.0;
  519.         *(a+3) = 0.0;
  520.     }
  521.     *(a+2) = exp( -twopi * bw / srate );
  522.     c = *(a+2) + 1.0;
  523.     *(a+1) = 4.0 * *(a+2) / c * cos(twopi * cf / srate );
  524.     if ( scl > 1.0 )
  525.         *a = sqrt((1.0 - *(a+2)) / c * (c * c - *(a+1) * *(a+1)));
  526.     else if ( scl < 1.0)
  527.         *a = 1.0;
  528.     else
  529.         *a = (1.0 - *(a+2)) * sqrt(1.0 - *(a+1) * *(a+1) / (4.0 * *(a+2)));
  530. }
  531.  
  532. double reson( x, a )
  533.     double    x, *a;
  534. {
  535. /* y[i] = a[0] * x[i] + a[1] * y[i-1] - a[2] * y[i-2] */
  536.  
  537.     register    double    y = *a * x + *(a+1) * *(a+3) - *(a+2) * *(a+4);
  538.     *(a+4) = *(a+3);
  539.     *(a+3) = y;
  540.     return(y);
  541. }
  542.  
  543.  
  544. void vrsset( pk, xinit, a )
  545.     double    pk, xinit, *a;
  546. {
  547.     if ( xinit <= 0.0 ) {
  548.         *(a+4) = 0.0;
  549.         *(a+3) = 0.0;
  550.     }
  551. /* *(a+1) and *(a+2) to be set during playing time */
  552.     *a = 1.0 / pk;
  553. }
  554.  
  555. double vreson(xin, cf, bw, fl, fno, a)
  556.     double    xin, cf, bw, fl, *a;
  557.     int    fno;
  558. {
  559.     register    double    y;
  560.     register    double    pi = 4.0 * atan(1.0);
  561.     register    double    x = 1.0 - pi * bw / srate;
  562.     *(a+2) = x * x;
  563.     x = 4.0 * *(a+2) / (1.0 + *(a+2));
  564.     y = fl * cf / srate;
  565.     *(a+1) = vfmult(x, y, fno);
  566.     return( reson(xin, a));
  567. }
  568.     
  569.  
  570.  
  571. void mono(output)
  572.     double output;
  573. {
  574.     *(out+loc) += output;
  575. }
  576.  
  577. void output(a, b, c, d)
  578.     double    a, b, c, d;
  579. {
  580.     switch(nchnls) {
  581.         case 4: *(out+loc+3) += d;
  582.         case 3: *(out+loc+2) += c;
  583.         case 2: *(out+loc+1) += b;
  584.         case 1: *(out+loc) += a;
  585.     }
  586. }
  587.  
  588. void stereo(output, prop)
  589.     double    output, prop;
  590. {
  591.     *(out+loc) += output * prop;
  592.     *(out+loc+1) += output * (1.0 - prop);
  593. }
  594.  
  595. double ilookup(x, fno)
  596.     double x;
  597.     int fno;
  598. {
  599.     /* interpolating table lookup */
  600.     register    double frac;
  601.     register  k;
  602.     int l;
  603.  
  604.     k = (int)x;
  605.     if ( k < 1 ) 
  606.         return( *(F[fno] + 1) );
  607.     else if ( k >= *(F[fno]) )
  608.         return( *(F[fno]+(int)*(F[fno])) );
  609.     else {
  610.         l = k + 1;
  611.         frac = x - k;
  612.         return(*(F[fno]+k) + ( *(F[fno]+l) - *(F[fno]+k)) * frac);
  613.     }
  614. }
  615.         
  616. double vfmult(amp, sl, fno)
  617.     double    amp, sl;
  618.     int    fno;
  619. {
  620.     register  k = ((int)sl % (int)(*(F[fno]))) + 1;
  621.     return( amp * *(F[fno] + k));
  622. }
  623.  
  624. double cpsoct(oct)
  625.     double    oct;
  626. {
  627.     /* linear octave form to cps, Mid C = octave 8 */
  628.     return( pow(2.0, oct) * 1.021975);
  629. }
  630.  
  631. double cpspch(pch)
  632.     double pch;
  633. {
  634.     /* 8ve.pc to cps */
  635.     register    double    oct = (int)pch;
  636.     return( pow(2.0, oct + 8.333333 * (pch-oct)) * 1.021975);
  637. }
  638.  
  639. double cycle(cps)
  640.     double cps;
  641. {
  642.     /* cps to samp inc */
  643.     return(cps * 512.0 / srate);
  644. }
  645.  
  646. double octave(oct)
  647.     double    oct;
  648. {
  649.     /* linear octave form to samp inc */
  650.     return( pow(2.0, oct) * 523.2511 / srate);
  651. }
  652.  
  653. double octcps(cps)
  654.     double    cps;
  655. {
  656.     /* cps to linear octave form */
  657.     return( log( cps / 1.021975 ) / 0.69314718);
  658. }
  659.  
  660. double octpch(pch)
  661.     double    pch;
  662. {
  663.     /* 8ve.pc to linear octave */
  664.     register    double oct = (int)pch;
  665.     return( oct + 8.333333 * (pch - oct));
  666. }
  667.  
  668. double pchcps(cps)
  669.     double cps;
  670. {
  671.     /* cps to 8ve.pc */
  672.     return(pchoct(octcps(cps)));
  673. }
  674.  
  675. double pchoct(oct)
  676.     double oct;
  677. {
  678.     /* linear octave form to 8ve.pc */
  679.     register    double    pch = (int)oct;
  680.     return((0.12 * ( oct - pch)) + pch);
  681. }
  682.  
  683. double period(dur)
  684.     double dur;
  685. {
  686.     /* duration to samp inc */
  687.     return(512.0 / srate / dur);
  688. }
  689.  
  690. double pitch(pch)
  691.     double pch;
  692. {
  693.     /* 8ve.pc to samp inc */
  694.     register    double oct = (int)pch;
  695.     return( pow(2.0, oct + 8.333333 * (pch-oct) ) * 523.2511 / srate);
  696. }
  697.  
  698. double sicps(si)
  699.     double si;
  700. {
  701.     /* samp inc to cps */
  702.     return((si * srate) / 512.0);
  703. }
  704.  
  705. double random(x)    /* !!! there is a Mac ToolBox call, Random */
  706.     double    *x;
  707. {
  708.     long    n = *x * 1048576.0;
  709.     *x = (double)( ((1061L * n + 221589L) % 1048576L)) / 1048576.0;
  710.     return(*x);
  711. }
  712.  
  713. double drand(amp, a)
  714.     double    amp, *a;
  715. {
  716.     *a = random(a);
  717.     return( amp * ( 1.0 - (2.0 * *a)));
  718. }
  719.  
  720. double randf(oldval, factor, seed)
  721.     double    oldval, factor, *seed;
  722. {
  723.     register    double    range = 2.0 - ( 2.0 * factor);
  724.     register    double    lowbnd,    uprbnd;
  725.     lowbnd = oldval - range;
  726.     if ( lowbnd < -1.0) lowbnd = -1.0;
  727.     uprbnd = oldval + range;
  728.     if ( uprbnd > 1.0) uprbnd = 1.0;
  729.     return(lowbnd + ((uprbnd-lowbnd) * random(seed)));
  730. }
  731.     
  732.  
  733. double randfc(amp, freq, a, curv, cdiff)
  734.     double    amp, freq, *a, curv[], cdiff[];
  735. {
  736. /* freq in Hz
  737. * *a = seed, (1.0 to init)
  738. * a[1] = oldval (0.0)
  739. * a[2] = diff   (0.0)
  740. * a[3] = phs    (0.0)
  741. * a[4] = factor (0.0...1.0)
  742. */
  743.     register    double t, indx;
  744.     register  i;
  745.  
  746.     indx = ((127.0 / srate) * *(a+3) * freq );
  747.     if ( indx > 127.0) {
  748.         *(a+3) = 0.0;
  749.         indx = 0;
  750.     }
  751.     if ( *(a+3) == 0.0 ) {
  752.         *(a+1) += *(a+2);
  753. /*        *(a+2) = randf( *(a+1), *(a+4), a) - *(a+1);*/
  754.         *(a+2) = randf( a[1], a[4], &a[0]) - *(a+1);
  755.     }
  756.     *(a+3) += 1.0;
  757.     i = (int)indx;
  758.     t = *(curv+i) + (*(cdiff+i) * ( indx - i));
  759.     t = ( amp * ( *(a+1) + ( t * *(a+2))));
  760.     return(t);
  761. }
  762.  
  763. double randfi(amp, freq, a )
  764.     double    amp, freq, *a;
  765. {
  766. /* freq in Hz
  767. * *a = seed, (1.0 to init)
  768. * a[1] = oldval (0.0)
  769. * a[2] = diff   (0.0)
  770. * a[3] = phs    (0.0)
  771. * a[4] = factor (0.0...1.0)
  772. */
  773.     register    double interp = *(a+3) / (srate / freq);
  774.     if ( interp >= 1.0) {
  775.         *(a+3) = 0.0;
  776.         interp = 0.0;
  777.     }
  778.     if ( *(a+3) == 0.0 ) {
  779.         *(a+1) += *(a+2);
  780.         *(a+2) = randf( *(a+1), *(a+4), a ) - *(a+1);
  781.     }
  782.     *(a+3) += 1.0;
  783.     return( amp * ( *(a+1) + ( interp * *(a+2)) ));
  784. }
  785.  
  786. double randh(amp, si, a)
  787.     double    amp, si, *a;
  788. {
  789.     *(a) += si;
  790.     if ( *(a) >= 512.0) {
  791.         *(a+1) = random((a+1));
  792.         *(a) -= 512.0;
  793.     }
  794.     return( *(a+1) * amp );
  795. }
  796.  
  797. double randi(amp, si, a)
  798.     double    amp, si, *a;
  799. {
  800.     *(a) += (si / 512.0);
  801.     if ( *(a) > 1.0 )  {
  802.         *(a) -= 1.0;
  803.         *(a+1) = *(a+2);
  804.         *(a+2) = random( (a+2) );
  805.         *(a+3) = 2.0 * ( *(a+1) - *(a+2) );
  806.         *(a+1) = 1.0 - ( *(a+1) * 2.0 ) - (*(a+3) * *(a) );
  807.     }
  808.     return( ( *(a+1) + *(a+3) * *(a) ) * amp);
  809. }
  810.  
  811.  
  812.  
  813. double alpass(xin, rvt, a)
  814.     double    xin, rvt, *a;
  815. {
  816.     register  l;
  817.     register    double x = comb(xin, rvt, a);
  818.     l = *(a+4);
  819.     return( x - *(a+3) * *(a+l) );
  820. }
  821.  
  822. double balnce(y, x, a)
  823.     double    y, x, *a;
  824. {
  825.     register    double q = tone(y * y, (a+3));
  826.     if ( q == 0.0 ) q = 0.00000001;
  827.     return( y * sqrt( tone(x * x, a)) / q);
  828. }
  829.  
  830. double comb(xin, rvt, a)
  831.     double    xin, rvt, *a;
  832. {
  833.     register  k;
  834.     register    double sig;
  835.     if ( rvt != *(a+2)) {
  836.         if ( rvt == 0.0 )
  837.             *(a+3) = 0.0;
  838.         else
  839.             *(a+3) = pow(0.001, *(a+1) / rvt );
  840.         *(a+3) = 0.0;
  841.         *(a+2) = rvt;
  842.     }
  843.     if ( *(a+4) >= *(a))
  844.         *(a+4) = 5.0;
  845.     else
  846.         *(a+5) += 1.0;
  847.     k = (long)*(a+4);
  848.     sig = *(a+k);
  849.     *(a+k) = (*(a+k) * *(a+3)) + xin;
  850.     return(sig);
  851. }
  852.  
  853.  
  854. void coscurv(curv, cdiff)
  855.     double    curv[];
  856.     double    cdiff[];
  857. {
  858.     register    double    pi = 4.0 * atan(1.0);
  859.     register  i;
  860.  
  861.     for ( i = 0; i < 128; i++)
  862.         *(curv+i) = (1.0 - cos(pi * (i/127.0))) * 0.5;
  863.     for ( i = 0; i < 127; i++)
  864.         *(cdiff+i) = *(curv+i+1) - *(curv+i);
  865.     *(cdiff+127) = 0.0;
  866. }
  867.  
  868. double buzz(amp, si, hn, fno, phs )
  869.     double    amp, si, hn, *phs;
  870.     int    fno;
  871. {
  872.     register  j = *phs;
  873.     register  k = (j+1) % 1024;
  874.     double    sig;
  875.     register    double h2n = 2.0 * hn;
  876.     register    double h2np1 = h2n + 1.0;
  877.     register    double    q = (int)( (*phs - (int)*phs) * h2np1) / h2np1;
  878.     double    d = *(F[fno] + j + 1);
  879.     double    e = *(F[fno] + k + 1);
  880.     d +=  (e - d) * q;
  881.     if ( d == 0.0 )
  882.         sig = amp;
  883.     else {
  884.         k = (int)(h2np1 * *phs) % 1024;
  885.         sig =  amp * (*(F[fno] + k + 1) / d - 1.0) / h2n;
  886.     }
  887.     *phs += si;
  888.     while (*phs >= 1024.0) *phs -= 1024.0;
  889.     return(sig);
  890. }
  891.  
  892.  
  893. void rvbset(xinit, a)
  894.     double    xinit, *a;
  895. {
  896.     register  i;
  897.     register  j;
  898.     void cmbset();
  899.     double xl[6];
  900.  
  901.     xl[0] = 0.0297;
  902.     xl[1] = 0.0371;
  903.     xl[2] = 0.0411;
  904.     xl[3] = 0.0437;
  905.  
  906.     xl[4] = 0.005;
  907.     xl[5] = 0.0017;
  908.  
  909.     j = 0;
  910.     for (i = 0; i < 6; i++ ) {
  911.         cmbset( xl[i], xinit, a+j );
  912.         j += (long)*(a+j);
  913.     }
  914. }
  915.  
  916. double reverb(xin, rvt, a )
  917.     double xin, rvt, *a;
  918. {
  919. /* after Schroeder */
  920. /* dimension for "a" is (30 + 1538 * srate / 10000) - 1 */
  921.     double x;
  922.     register  i;
  923.     register  j;
  924.  
  925.     x = 0.0;
  926.     j = 0;
  927.     for ( i = 0; i < 4; i++ ) {
  928.         x += comb(xin, rvt, a+j );
  929.         j += (long)*(a+j);
  930.     }
  931.     x = alpass(x, 0.096835, a+j) * 0.25;
  932.     j += (long)*(a+j);
  933.     return( alpass(x, 0.32924, a+j));
  934. }
  935.  
  936. void rvb2set(rvt, xinit, a, b )
  937.     double rvt, xinit, *a, *b;
  938. {
  939. /*
  940. * Reverb unit consists of 6 combs in parallel, followed by 1 alpass filter.
  941. * Combs each have a low pass filter built in.
  942. * b[0] to b[5] = delay times (in seconds) for the comb filters.
  943. * b[6] = delay time (in seconds) for the alpass filter.
  944. *
  945. * b[7] to b[12] = gains for low pass filters in combs.
  946. * b[13] = gain for alpass.
  947. *
  948. * if b[0] = 0.0 fixed data (as below) is used, this was taken from
  949. * Andy Moorer's "About this Reverberation Business" and is for 16.66kHz
  950. * sampling rate.
  951. *
  952. * Gains for filters (g2) are calculated as follows:
  953. *    g2 = gain * (1.0 - g1)
  954. * where g1 is the low pass filter gain and "gain" is calculated from approx.
  955. *    gain = 1.0 - ( 0.366 / reverb_time )
  956. *
  957. * Dimension of array "a" is given by the sum of
  958. *    (delay_time * sampling_rate) + 5.5 for each comb and alpass.
  959. *    = 6557 for the fixed data at srate = 166667.
  960. *   = 7850 for 20000
  961. */
  962.  
  963.     double del[7];
  964.     double filtg[7];
  965.     double gain;
  966.     register  i;
  967.     register  j;
  968.     int lj;
  969.     int n;
  970.     
  971.     if ( *b == 0.0) {
  972.         *del = 0.05;
  973.         *(del+1) = 0.056;
  974.         *(del+2) = 0.061;
  975.         *(del+3) = 0.068;
  976.         *(del+4) = 0.072;
  977.         *(del+5) = 0.078;
  978.         *(del+6) = 0.006;
  979.  
  980.         *filtg = 0.172;
  981.         *(filtg+1) = 0.179;
  982.         *(filtg+2) = 0.187;
  983.         *(filtg+3) = 0.194;
  984.         *(filtg+4) = 0.198;
  985.         *(filtg+5) = 0.205;
  986.         *(filtg+6) = 0.7;
  987.     }
  988.     else {
  989.         *del = *b;
  990.         *(del+1) = *(b+1);
  991.         *(del+2) = *(b+2);
  992.         *(del+3) = *(b+3);
  993.         *(del+4) = *(b+4);
  994.         *(del+5) = *(b+5);
  995.         *(del+6) = *(b+6);
  996.  
  997.         *filtg = *(b+7);
  998.         *(filtg+1) = *(b+8);
  999.         *(filtg+2) = *(b+9);
  1000.         *(filtg+3) = *(b+10);
  1001.         *(filtg+4) = *(b+11);
  1002.         *(filtg+5) = *(b+12);
  1003.         *(filtg+6) = *(b+13);
  1004.     }
  1005.     gain = 1.0 - ( 0.366 / rvt);
  1006.  
  1007. /*
  1008. * *(a+j) = buffer length
  1009. * *(a+j+1) = g2, gain of comb
  1010. * *(a+j+2) = g1, gain factor
  1011. * *(a+j+3) = previous sample for comb lpf
  1012. * *(a+j+4) = ptr
  1013. */
  1014.  
  1015.     j = 0;
  1016.     for ( i = 0; i < 6; i++ ) {
  1017.         *(a+j) = 4.0 + (long)( *(del+i) * srate + 0.5);
  1018.         *(a+j+1) = gain * ( 1.0 - *(filtg+i));
  1019.         *(a+j+2) = *(filtg+i);
  1020.         *(a+j+3) = 0.0;
  1021.         *(a+j+4) = 4.0;
  1022.         lj = j + 5;
  1023.         j += (long) *(a+j);
  1024.         if ( xinit <= 0.0 ) {
  1025.             for ( n = lj; n < j; n++)
  1026.                 *(a+n) = 0.0;
  1027.         }
  1028.     }
  1029. /* alpass */
  1030.     *(a+j) = 4.0 + (long)( *(del+i) * srate + 0.5);
  1031.     *(a+j+1) = *(filtg+i);
  1032.     *(a+j+2) = 0.0;
  1033.     *(a+j+3) = 0.0;
  1034.     *(a+j+4) = 4.0;
  1035.     lj = j + 5;
  1036.     j += (long) *(a+j);
  1037.     if ( xinit <= 0.0 ) {
  1038.         for ( n = lj; n < j; n++)
  1039.             *(a+n) = 0.0;
  1040.     }
  1041. }
  1042.  
  1043. double reverb2(xin, a)
  1044.     double xin, *a;
  1045. {
  1046.     register    double x;
  1047.     register  i;
  1048.     register  j;
  1049.     j = 0;
  1050.     x = 0.0;
  1051.     for ( i = 0; i < 6; i++ ) {
  1052. /*        *(a+j+2) = comb2(xin, a+j) + (*(a+j+2) * *(a+j+1));
  1053.         x += *(a+j+2);
  1054. */
  1055.         x += comb2(xin, a+j);
  1056.         j += (long) *(a+j);
  1057.     }
  1058.     return( alpass2(x, a+j) );
  1059. }
  1060.  
  1061. double alpass2(xin, a)
  1062.     double    xin, *a;
  1063. {
  1064.     register    double x = comb2(xin, a);
  1065.     int l;
  1066.     if ( *(a+4) >= *a)
  1067.         *(a+4) = 5.0;
  1068.     if ( *(a+4) >= *a-1.0)
  1069.         ;
  1070.     l = (long)*(a+4);
  1071.     return( x - *(a+1) * *(a+l) );
  1072. }
  1073.  
  1074. double comb2(xin, a )
  1075.     double    xin, *a;
  1076. {
  1077.     register  k;
  1078.     register  l;
  1079.     register    double sig;
  1080.     if (*(a+4) < ( *a - 2.0 ) ) {
  1081.         *(a+4) += 1.0;
  1082.         l = (long) *(a+4);
  1083.         k = l + 1;
  1084.     }
  1085.     else if ( *(a+4) == (*a - 2.0)) {
  1086.         *(a+4) += 1.0;
  1087.         l = (long)*(a+4);
  1088.         k = 5;
  1089.     }
  1090.     else {
  1091.         *(a+4) = 5.0;
  1092.         l = 5;
  1093.         k = 6;
  1094.     }
  1095.     sig = *(a+k);
  1096.     *(a+l) = xin + ( *(a+1) * (*(a+k) + (*(a+2) * *(a+l))));
  1097.     return(sig);
  1098. }
  1099.  
  1100.  
  1101.  
  1102. double zdelay(sigin, delay_len, buflen, buf, bufptr)
  1103.     double    sigin, delay_len, *buf, *bufptr;
  1104.     int    buflen;
  1105. {
  1106.     register  i;
  1107.     register  k;
  1108.     register  j;
  1109.     register    double    delsamp;
  1110.     double    frac;
  1111.     register    double    temp;
  1112.     
  1113. /* first, get the array index */
  1114.     k = (int)*bufptr;
  1115.     
  1116.     if ( k >= buflen) {
  1117.         k = 0;
  1118.     }
  1119. /* stuff the new sample into the buffer */
  1120.     *(buf+k) = sigin;
  1121. /* get the delayed sample's index, and check it's within range */
  1122.     delsamp = *bufptr - delay_len;
  1123.     if ( delsamp < 0.0 ) delsamp += buflen;
  1124.     if ( delsamp >= buflen ) delsamp -= buflen;
  1125. /* ok, inc and check new sample index */
  1126.     (*bufptr)++;
  1127.     if ( *bufptr >= buflen )
  1128.         *bufptr = 0.0;
  1129. /* get integer indices, will have to wrap around if i is at end of buffer */
  1130.     i = (int)delsamp;
  1131.     if ( i < (buflen-1) )
  1132.         j = i+1;
  1133.     else
  1134.         j = 0;
  1135.     frac = delsamp - i;
  1136.     temp = *(buf+i);
  1137.     temp += ((*(buf+j) - temp) * frac );
  1138.     return(temp);
  1139. }
  1140.  
  1141. double sdelay(delay_len, buflen, buf, bufptr)
  1142.     double    delay_len, *buf, *bufptr;
  1143.     int    buflen;
  1144. {
  1145.     register  i;
  1146.     register  j;
  1147.     double    frac;
  1148.     register    double    delsamp = *bufptr - delay_len;
  1149.     register    double    temp;
  1150.     
  1151.     if ( delsamp < 0.0 ) delsamp += buflen;
  1152.     if ( delsamp >= buflen ) delsamp -= buflen;
  1153.     i = (int)delsamp;
  1154.     if ( i < (buflen-1) )
  1155.         j = i+1;
  1156.     else
  1157.         j = 0;
  1158.     frac = delsamp - i;
  1159.     temp = *(buf+i);
  1160.     temp += ((*(buf+j) - temp) * frac );
  1161.     return(temp);
  1162. }
  1163.  
  1164.  
  1165.  
  1166.  
  1167.  
  1168. read_set(fname, buf, buflen, bptr, fildes)
  1169.     char    *fname;
  1170.     float    buf[];
  1171.     int        buflen;
  1172.     double    *bptr;
  1173.     int        *fildes;
  1174. {
  1175.     register  i;
  1176.     long    pos, lseek();
  1177.     int        nread, recno;
  1178.  
  1179.     for (i = 0; i < buflen; i++ )
  1180.         *(buf+i) = 0.0;
  1181.  
  1182.     if ((*fildes = open(fname, 0)) != -1) {
  1183.         recno = (int)(*bptr / buflen);
  1184.         *bptr -= (double)(recno * buflen);
  1185.         nread = 0;
  1186.         pos = lseek(*fildes, (long)(recno*buflen*sizeof(float)), nread);
  1187.         if ( (nread = read(*fildes, (char *)buf, (unsigned)(buflen * sizeof(float)) )) == -1){
  1188.             PstringCopy((char *)theMess1, "\pread failed in read_set");
  1189.             OSError(theMess1, NIL, theErr);
  1190.         }
  1191.     }
  1192.     else {
  1193.         PstringCopy((char *)theMess1, "\pfailed to open sound file");
  1194.         OSError(theMess1, NIL, theErr);
  1195.     }
  1196. }
  1197.  
  1198. double    readsfi(fildes, si, buf, buflen, bptr)
  1199.     int    fildes;
  1200.     int    buflen;
  1201.     double    si, *bptr;
  1202.     float    buf[];
  1203. {
  1204. /*
  1205. * interpolating soundfile read,
  1206. * negative and fractional sample increments are accommodated. 
  1207. */
  1208.     register  i;
  1209.     register  k;
  1210.     double    frac;
  1211.     double    oldsamp;
  1212.     long    pos, lseek();
  1213.     int        nread;
  1214.     int        new_read;
  1215.     long    reclen = buflen * sizeof(float);
  1216.  
  1217.     new_read = 0;
  1218. /* ensure *bptr points to somewhere within the current record */
  1219.     if ( *bptr < -reclen ) {
  1220.         *bptr += si;
  1221.         return(0.0);
  1222.     }
  1223.     while ( *bptr < 0.0 ) {
  1224.         pos = lseek(fildes, -reclen, 1 );
  1225.         *bptr += buflen;
  1226.         new_read = -1;
  1227.     }
  1228.     while ( *bptr >= buflen ) {
  1229.         *bptr -= buflen;
  1230.         new_read = 1;
  1231.         if ( *bptr >= buflen )
  1232.             pos = lseek(fildes, reclen, 1 );
  1233.     }
  1234.     if ( new_read == -1) {
  1235.         pos = lseek(fildes, -reclen, 1 );
  1236.         if ( pos < 0 ) {
  1237.             *bptr += si;
  1238.             for (i = 0; i < buflen; i++ )
  1239.                 *(buf+i) = 0.0;
  1240.             return(0.0);
  1241.         }
  1242.         if ((nread = read(fildes, (char *)buf, (unsigned)reclen)) == -1) {
  1243.             perror("read failed in readsfi (new_read = -1)");
  1244.             return(0.0);
  1245.         }
  1246.     }
  1247.     else if ( new_read == 1) {
  1248.         if ( (nread = read(fildes, (char *)buf, (unsigned)reclen)) == -1 ) {
  1249.             perror("read failed in readsfi (new_read = 1)");
  1250.             return(0.0);
  1251.         }
  1252.         if ( nread < (int)reclen ) { 
  1253.             for ( i = (int)(nread/sizeof(float)); i < buflen; i++ ) {
  1254.                 *(buf+i) = 0.0;
  1255.             }
  1256.         }
  1257.     }
  1258.  
  1259.     /* now check for interpolation */
  1260.     i = (int)*bptr;
  1261.     frac = *bptr - i;
  1262.     *bptr += si;
  1263.     if ( frac == 0.0) {
  1264.         return( *(buf+i) );
  1265.     }
  1266.     k = i + 1;
  1267.     /* check if sample k is in this record */
  1268.     oldsamp = *(buf+i);
  1269.     if ( k >= buflen ) {
  1270.         /*pos = lseek(fildes, reclen, 1 );*/
  1271.         *bptr -= buflen;
  1272.         k = 0;
  1273.         if ((nread = read(fildes, (char *)buf, (unsigned)reclen)) == -1 ) {
  1274.             perror("read failed in readsfi near end of routine");
  1275.             return(0.0);
  1276.         }
  1277.         if ( nread < (int)reclen ) { 
  1278.             for ( i = (nread/sizeof(float)); i < buflen; i++ ) {
  1279.                 *(buf+i) = 0.0;
  1280.             }
  1281.         }
  1282.     }
  1283.     return( oldsamp + ( (*(buf+k) - oldsamp) * frac ) );
  1284. }
  1285.  
  1286.  
  1287.  
  1288.  
  1289.  
  1290. Boolean SF_FLOAT_ReadSet(buf, buflen, bptr, myPBlkPtr, SampPtr, StartSamp, EndSamp)
  1291.     double    *buf;
  1292.     int        buflen;
  1293.     double    *bptr, *SampPtr;
  1294.     long    *StartSamp, *EndSamp;
  1295.     ParmBlkPtr        myPBlkPtr;
  1296. {
  1297.  
  1298. /* set file pos and  get the buffer full*/
  1299.     register    i;
  1300.     long    nBytes;
  1301.     float    *fptr1, *fptr2;
  1302.     double    *dptr;
  1303.     long    nSamps;
  1304.     long    theLastSamp;
  1305.     long    nrecs;
  1306.     
  1307.     fptr1 = (float *)NewPtr(buflen * sizeof(float) );
  1308.     if ( fptr1 == NIL ) {
  1309.         PstringCopy((char *)theMess1, "\pNot enough memory in MACread_set");
  1310.         OSError(theMess1, NIL, theErr);
  1311.     }
  1312.     for (i = 0, dptr = buf; i < buflen; i++ )
  1313.      *dptr++ = 0.0;
  1314.     for (i = 0, fptr2 = fptr1; i < buflen; i++ )
  1315.      *fptr2++ = 0.0;
  1316.  
  1317.  
  1318. /* StartSamp points to the actual sample number */
  1319.     myPBlkPtr->ioParam.ioPosMode = fsFromStart;
  1320.     myPBlkPtr->ioParam.ioCompletion = NIL;
  1321. /* we round off to a buffer boundary */
  1322.     myPBlkPtr->ioParam.ioPosOffset = (long)(*StartSamp * sizeof(float));
  1323.     myPBlkPtr->ioParam.ioBuffer = (Ptr)fptr1;
  1324.     myPBlkPtr->ioParam.ioReqCount = (long)(buflen*sizeof(float));
  1325.     *SampPtr = (double)*StartSamp;
  1326.     *EndSamp = *StartSamp + buflen;
  1327.     *bptr = 0.0;
  1328.     theErr = PBRead(myPBlkPtr, FALSE);
  1329.     if (theErr != noErr ) {
  1330.         if ( theErr == eofErr ) {
  1331.         /* round off to a record boundary and read the
  1332.             remaining portion of the file into the buffer */
  1333.             myPBlkPtr->ioParam.ioCompletion = NIL;
  1334.             theErr = PBGetEOF(myPBlkPtr, FALSE);
  1335.             theLastSamp = (long)myPBlkPtr->ioParam.ioMisc / sizeof(float);
  1336.             nrecs = (long)theLastSamp / buflen;
  1337.             *StartSamp = nrecs * buflen;
  1338.             myPBlkPtr->ioParam.ioPosMode = fsFromStart;
  1339.             myPBlkPtr->ioParam.ioCompletion = NIL;
  1340.             myPBlkPtr->ioParam.ioPosOffset = (long)(*StartSamp * sizeof(float));
  1341.             myPBlkPtr->ioParam.ioReqCount = (theLastSamp - *StartSamp) * sizeof(float);
  1342.             theErr = PBRead(myPBlkPtr, FALSE);
  1343.             *EndSamp = theLastSamp;
  1344.             *bptr = (*EndSamp - *StartSamp) - 1;
  1345.             *SampPtr = (double)*EndSamp-1;
  1346.         }
  1347.         else {
  1348.             PstringCopy((char *)theMess1, "\pError reading from the soundfile");
  1349.             OSError(theMess1, NIL, theErr);
  1350.         }
  1351.     }
  1352.     else {
  1353.         *bptr = 0.0;
  1354.         *EndSamp = *StartSamp + buflen;
  1355.     }
  1356.     
  1357.     nBytes = myPBlkPtr->ioParam.ioActCount;
  1358.     nSamps = nBytes / sizeof(float);
  1359.     for ( i = 0, dptr = buf, fptr2 = fptr1; i < nSamps; i++ )
  1360.         *dptr++ = (double)*fptr1++;
  1361.     DisposPtr((Ptr)fptr1);
  1362.     DisposPtr((Ptr)fptr2);
  1363.     DisposPtr((Ptr)dptr);
  1364.     return(TRUE);
  1365. }
  1366.  
  1367.  
  1368.  
  1369.  
  1370. double    SF_FLOAT_Read(myPBlkPtr, si, buf, buflen, bptr, SampPtr, StartSamp, EndSamp)
  1371.     ParmBlkPtr        myPBlkPtr;
  1372.     int                buflen;
  1373.     double            si;
  1374.     double             *bptr;        /* points to a sample no WITHIN the buffer */
  1375.     double            *buf;
  1376.     long            *StartSamp, *EndSamp;
  1377.     double            *SampPtr;
  1378. {
  1379. /*
  1380. * interpolating soundfile read,
  1381. * negative and fractional sample increments are accommodated. 
  1382. */
  1383.     register  i;
  1384.     register  k;
  1385.     register    double    frac;
  1386.     register    double    thisSamp;
  1387.     float    oldSamp, *PtrToOldSamp;
  1388.     long    nBytes;
  1389.     float    *Fptr;
  1390.     long    nSamps;
  1391.  
  1392.  
  1393.     if ( *SampPtr < (double)*StartSamp ) {    /* read previous buffer */
  1394.         if ( *SampPtr < 0 )
  1395.             return(0.0);
  1396.         Fptr = (float *)NewPtr(buflen * sizeof(float) );
  1397.         /* zero out the buffers */
  1398.         for (i = 0; i < buflen; i++ ) *(buf+i) = 0.0;
  1399.         for (i = 0; i < buflen; i++ ) *(Fptr+i) = 0.0;
  1400.         myPBlkPtr->ioParam.ioBuffer = (Ptr)Fptr;
  1401.         *EndSamp = *StartSamp;
  1402.         *StartSamp = *EndSamp - buflen;
  1403.         *bptr += buflen;
  1404.         if ( *StartSamp < 0L ) {
  1405.             *StartSamp = 0L;
  1406.             myPBlkPtr->ioParam.ioReqCount =
  1407.                 (long) ((*EndSamp - *StartSamp) * sizeof(float));
  1408.         }
  1409.         else {
  1410.             myPBlkPtr->ioParam.ioReqCount = (long)(buflen*sizeof(float));
  1411.         }
  1412.         
  1413.         
  1414.         myPBlkPtr->ioParam.ioPosOffset = (long)(*StartSamp*sizeof(float));
  1415.         theErr = PBRead(myPBlkPtr, FALSE);
  1416.         if ( theErr != noErr ) {
  1417.             if ( myPBlkPtr->ioParam.ioPosOffset < NIL || theErr == eofErr || theErr == posErr )
  1418. /*            mark is outside file bounds (= %ld\n", myPBlkPtr->ioParam.ioPosOffset;*/
  1419.                 ;
  1420.             *SampPtr += si;
  1421.             *bptr += si;
  1422.             return(0.0);
  1423.         }
  1424.         /* otherwise */
  1425.         nBytes = myPBlkPtr->ioParam.ioActCount;
  1426.         nSamps = nBytes / sizeof(float);
  1427.         for ( i = 0; i < nSamps; i++ )
  1428.             *(buf+i) = (double)*(Fptr+i);
  1429.         DisposPtr((Ptr)Fptr);
  1430.     }
  1431.     else if ( *SampPtr >= (double)*EndSamp ) {    /* read next bufferful */
  1432.     /* works ok for p[os si gg12/6/90 */
  1433.         if ( *StartSamp >= *EndSamp )    /* must have already read past EOF */
  1434.             return(0.0);
  1435.         Fptr = (float *)NewPtr(buflen * sizeof(float) );
  1436.         /* zero out the buffers */
  1437.         for (i = 0; i < buflen; i++ ) *(buf+i) = 0.0;
  1438.         for (i = 0; i < buflen; i++ ) *(Fptr+i) = 0.0;
  1439.         myPBlkPtr->ioParam.ioBuffer = (Ptr)Fptr;
  1440.         *StartSamp = (long)*SampPtr;
  1441.         *EndSamp = *StartSamp + buflen;
  1442.         *bptr -= buflen;
  1443.         myPBlkPtr->ioParam.ioPosOffset = (long)(*SampPtr*sizeof(float));
  1444.         myPBlkPtr->ioParam.ioReqCount = (long)(buflen*sizeof(float));
  1445.         theErr = PBRead(myPBlkPtr, FALSE);
  1446.         if ( theErr != noErr ) {
  1447.             if ( theErr == eofErr ) {
  1448.                 if (myPBlkPtr->ioParam.ioActCount == 0L ) {
  1449.                     DisposPtr((Ptr)Fptr);
  1450.                     *SampPtr = (double)*EndSamp;
  1451.                     *StartSamp = *EndSamp;
  1452.                     *SampPtr += si;
  1453.                     *bptr += si;
  1454.                     return(0.0);
  1455.                 }
  1456.                 *EndSamp = *StartSamp +
  1457.                     (myPBlkPtr->ioParam.ioActCount / sizeof(float));
  1458.             }
  1459.             if ( myPBlkPtr->ioParam.ioPosOffset < NIL || theErr == eofErr || theErr == posErr )
  1460. /*            mark is outside file bounds (= %ld\n", myPBlkPtr->ioParam.ioPosOffset;*/
  1461.                 ;
  1462.             DisposPtr((Ptr)Fptr);
  1463.         }
  1464.         /* otherwise */
  1465.         nBytes = myPBlkPtr->ioParam.ioActCount;
  1466.         nSamps = nBytes / sizeof(float);
  1467.         for ( i = 0; i < nSamps; i++ )
  1468.             *(buf+i) = (double)*(Fptr+i);
  1469.         DisposPtr((Ptr)Fptr);
  1470.     }
  1471.  
  1472.  
  1473.  
  1474.  
  1475.     /* now check for interpolation */
  1476.     i = (int)*bptr;
  1477.     frac = *bptr - i;
  1478.     *SampPtr += si;
  1479.     *bptr += si;
  1480.     if ( frac == 0.0) {
  1481.         return(*(buf+i) );
  1482.     }
  1483.     k = i + 1;
  1484.     /* check if sample k is in this record */
  1485.     thisSamp = *(buf+i);
  1486.     if ( k >= buflen ) {
  1487.         if ( si < 0.0 ) {
  1488.             /* we must have a negative, fractional sample increment, we have probably
  1489.             just read a new record and must now interpolate between th last sample in
  1490.             this rec and the first sample in the one we just discarded.  To save hassle,
  1491.             just read that sample in, do the interpolation and forget it! */
  1492.             PtrToOldSamp = &oldSamp;
  1493.             myPBlkPtr->ioParam.ioBuffer = (Ptr)PtrToOldSamp;
  1494.             myPBlkPtr->ioParam.ioPosOffset = (long)((*SampPtr+1.0)*sizeof(float));
  1495.             myPBlkPtr->ioParam.ioReqCount = (long)sizeof(float);
  1496.             theErr = PBRead(myPBlkPtr, FALSE);
  1497.             if ( theErr == noErr ) {
  1498.                 return( (double)(thisSamp + ( (oldSamp - thisSamp) * frac ) ));
  1499.             }
  1500.             /* problem reading the sample, just return the the current sample */
  1501.             return(thisSamp);
  1502.         }
  1503.         k = 0;
  1504.         Fptr = (float *)NewPtr(buflen * sizeof(float) );
  1505.         for (i = 0; i < buflen; i++ ) *(buf+i) = 0.0;
  1506.         for (i = 0; i < buflen; i++ ) *(Fptr+i) = 0.0;
  1507.         myPBlkPtr->ioParam.ioBuffer = (Ptr)Fptr;
  1508.         *StartSamp = (long)*SampPtr;
  1509.         *EndSamp = *StartSamp + buflen;
  1510.         myPBlkPtr->ioParam.ioPosOffset = (long)(*SampPtr*sizeof(float));
  1511.         myPBlkPtr->ioParam.ioReqCount = (long)(buflen*sizeof(float));
  1512.         theErr = PBRead(myPBlkPtr, FALSE);
  1513.         if ( theErr != noErr ) {
  1514.             if ( theErr == eofErr ) {
  1515.                 if (myPBlkPtr->ioParam.ioActCount == 0L ) {
  1516.                     DisposPtr((Ptr)Fptr);
  1517.                     *SampPtr = (double)*EndSamp;
  1518.                     *StartSamp = *EndSamp;
  1519.                     *SampPtr += si;
  1520.                     *bptr += si;
  1521.                     return(0.0);
  1522.                 }
  1523.                 *EndSamp = *StartSamp +
  1524.                     (myPBlkPtr->ioParam.ioActCount / sizeof(float));
  1525.             }
  1526.             else {
  1527.                 DisposPtr((Ptr)Fptr);
  1528.                 return(0.0);
  1529.             }
  1530.             if ( myPBlkPtr->ioParam.ioPosOffset < NIL || theErr == eofErr || theErr == posErr )
  1531.                 ;
  1532.             DisposPtr((Ptr)Fptr);
  1533.             return(0.0);
  1534.         }
  1535.         nBytes = myPBlkPtr->ioParam.ioActCount;
  1536.         nSamps = nBytes / sizeof(float);
  1537.         for ( i = 0; i < nSamps; i++ )
  1538.             *(buf+i) = (double)*(Fptr+i);
  1539.         DisposPtr((Ptr)Fptr);
  1540.         *bptr -= buflen;
  1541.     }
  1542.     return( (double)(thisSamp + ( (*(buf+k) - thisSamp) * frac ) ));
  1543. }
  1544. /*-------------------------------------------------------------------------------*/
  1545.  
  1546. Boolean SF_SD_1_ReadSet(buf, buflen, bptr, myPBlkPtr, SampPtr, StartSamp, EndSamp)
  1547.     double    *buf;
  1548.     int        buflen;
  1549.     double    *bptr, *SampPtr;
  1550.     long    *StartSamp, *EndSamp;
  1551.     ParmBlkPtr        myPBlkPtr;
  1552. {
  1553.  
  1554. /* set file pos and  get the buffer full*/
  1555.     register    i;
  1556.     long    nBytes;
  1557.     int    *iptr1, *iptr2;
  1558.     double    *dptr;
  1559.     long    nSamps;
  1560.     long    theLastSamp;
  1561.     long    nrecs;
  1562.     WaveRec    Header;
  1563.     WavPtr    HeaderPtr;
  1564.     
  1565. /* first, read the header info */
  1566.     HeaderPtr = &Header;
  1567.     
  1568.     nBytes = SD_HEADER_SIZE;
  1569.     myPBlkPtr->ioParam.ioPosMode = fsFromStart;
  1570.     myPBlkPtr->ioParam.ioPosOffset = 0L;
  1571.     myPBlkPtr->ioParam.ioBuffer = (Ptr)HeaderPtr;
  1572.     myPBlkPtr->ioParam.ioReqCount = nBytes;
  1573.     theErr = PBRead(&myPBlkPtr->ioParam, FALSE);
  1574.     if (theErr != noErr ) {
  1575.         PstringCopy((char *)theMess1, "\pError reading SD file Header");
  1576.         OSError(theMess1, NIL, theErr);
  1577.     }
  1578.     nSamps = Header.FileSize / sizeof(int);
  1579.     
  1580.     
  1581.     iptr1 = (int *)NewPtr(buflen * sizeof(int) );
  1582.     if ( iptr1 == NIL ) {
  1583.         PstringCopy((char *)theMess1, "\pNot enough memory in SF_SD_ReadSet");
  1584.         OSError(theMess1, NIL, theErr);
  1585.     }
  1586.     for (i = 0, dptr = buf, iptr2 = iptr1; i < buflen; i++ ) {
  1587.         *dptr++ = 0.0;
  1588.         *iptr2++ = 0;
  1589.     }
  1590.  
  1591. /* StartSamp points to the actual sample number, we add on header offset */
  1592.     *StartSamp += (SD_HEADER_SIZE / sizeof(int));
  1593.     myPBlkPtr->ioParam.ioPosMode = fsFromStart;
  1594.     myPBlkPtr->ioParam.ioCompletion = NIL;
  1595. /* we round off to a buffer boundary */
  1596.     myPBlkPtr->ioParam.ioPosOffset = (long)(*StartSamp * sizeof(int));
  1597.     myPBlkPtr->ioParam.ioBuffer = (Ptr)iptr1;
  1598.     myPBlkPtr->ioParam.ioReqCount = (long)(buflen*sizeof(int));
  1599.     *SampPtr = (double)*StartSamp;
  1600.     *EndSamp = *StartSamp + buflen;
  1601.     *bptr = 0.0;
  1602.     theErr = PBRead(myPBlkPtr, FALSE);
  1603.     if (theErr != noErr ) {
  1604.         if ( theErr == eofErr ) {
  1605.         /* round off to a record boundary and read the
  1606.             remaining portion of the file into the buffer */
  1607.             myPBlkPtr->ioParam.ioCompletion = NIL;
  1608.             theErr = PBGetEOF(myPBlkPtr, FALSE);
  1609.             theLastSamp = (long)myPBlkPtr->ioParam.ioMisc / sizeof(int);
  1610.             theLastSamp -= (SD_HEADER_SIZE / sizeof(int));
  1611.             nrecs = (long)theLastSamp / buflen;
  1612.             *StartSamp = (nrecs * buflen) + (SD_HEADER_SIZE / sizeof(int));
  1613.             myPBlkPtr->ioParam.ioPosMode = fsFromStart;
  1614.             myPBlkPtr->ioParam.ioCompletion = NIL;
  1615.             myPBlkPtr->ioParam.ioPosOffset = (long)(*StartSamp * sizeof(int));
  1616.             myPBlkPtr->ioParam.ioReqCount = (theLastSamp - *StartSamp) * sizeof(int);
  1617.             theErr = PBRead(myPBlkPtr, FALSE);
  1618.             *EndSamp = theLastSamp;
  1619.             *bptr = (*EndSamp - *StartSamp) - 1;
  1620.             *SampPtr = (double)*EndSamp-1;
  1621.         }
  1622.         else {
  1623.             PstringCopy((char *)theMess1, "\pError reading from the soundfile");
  1624.             OSError(theMess1, NIL, theErr);
  1625.         }
  1626.     }
  1627.     else {
  1628.         *bptr = 0.0;
  1629.         *EndSamp = *StartSamp + buflen;
  1630.     }
  1631.     
  1632.     nBytes = myPBlkPtr->ioParam.ioActCount;
  1633.     nSamps = nBytes / sizeof(int);
  1634.     for ( i = 0, dptr = buf, iptr2 = iptr1; i < nSamps; i++ )
  1635.         *dptr++ = (double)*iptr1++;
  1636.     DisposPtr((Ptr)iptr1);
  1637.     DisposPtr((Ptr)iptr2);
  1638.     DisposPtr((Ptr)dptr);
  1639.     return(TRUE);
  1640. }
  1641.  
  1642.  
  1643.  
  1644.  
  1645. double    SF_SD_1_Read(myPBlkPtr, si, buf, buflen, bptr, SampPtr, StartSamp, EndSamp)
  1646.     ParmBlkPtr        myPBlkPtr;
  1647.     int                buflen;
  1648.     double            si;
  1649.     double             *bptr;        /* points to a sample no WITHIN the buffer */
  1650.     double            *buf;
  1651.     long            *StartSamp, *EndSamp;
  1652.     double            *SampPtr;
  1653. {
  1654. /*
  1655. * interpolating soundfile read of Digidesign's Sound Designer¬ format files
  1656. * negative and fractional sample increments are accommodated. 
  1657. */
  1658.     register  i;
  1659.     register  k;
  1660.     register    double    frac;
  1661.     register    int    thisSamp;
  1662.     int    oldSamp, *PtrToOldSamp;
  1663.     long    nBytes;
  1664.     int    *Iptr;
  1665.     long    nSamps;
  1666.  
  1667.  
  1668.     if ( *SampPtr < (double)*StartSamp ) {    /* read previous buffer */
  1669.         if ( *SampPtr < (SD_HEADER_SIZE / sizeof(int)) )
  1670.             return(0.0);
  1671.         Iptr = (int *)NewPtr(buflen * sizeof(int) );
  1672.         /* zero out the buffers */
  1673.         for (i = 0; i < buflen; i++ ) *(buf+i) = 0.0;
  1674.         for (i = 0; i < buflen; i++ ) *(Iptr+i) = 0.0;
  1675.         myPBlkPtr->ioParam.ioBuffer = (Ptr)Iptr;
  1676.         
  1677.         *EndSamp = *StartSamp;
  1678.         *StartSamp = *EndSamp - buflen;
  1679.         *bptr += buflen;
  1680.         if ( *StartSamp < (SD_HEADER_SIZE / sizeof(int)) ) {
  1681.             *StartSamp = SD_HEADER_SIZE / sizeof(int);
  1682.             myPBlkPtr->ioParam.ioReqCount =
  1683.                 (long) ((*EndSamp - *StartSamp) * sizeof(int));
  1684.         }
  1685.         else {
  1686.             myPBlkPtr->ioParam.ioReqCount = (long)(buflen*sizeof(int));
  1687.         }
  1688.         
  1689.         
  1690.         myPBlkPtr->ioParam.ioPosOffset = (long)(*StartSamp*sizeof(int));
  1691.         theErr = PBRead(myPBlkPtr, FALSE);
  1692.         if ( theErr != noErr ) {
  1693.             if ( myPBlkPtr->ioParam.ioPosOffset < NIL || theErr == eofErr || theErr == posErr )
  1694. /*            mark is outside file bounds (= %ld\n", myPBlkPtr->ioParam.ioPosOffset;*/
  1695.                 ;
  1696.             *SampPtr += si;
  1697.             *bptr += si;
  1698.             return(0.0);
  1699.         }
  1700.         /* otherwise */
  1701.         nBytes = myPBlkPtr->ioParam.ioActCount;
  1702.         nSamps = nBytes / sizeof(int);
  1703.         for ( i = 0; i < nSamps; i++ )
  1704.             *(buf+i) = (double)*(Iptr+i);
  1705.         DisposPtr((Ptr)Iptr);
  1706.     }
  1707.     else if ( *SampPtr >= (double)*EndSamp ) {    /* read next bufferful */
  1708.         if ( *StartSamp >= *EndSamp )    /* must have already read past EOF */
  1709.             return(0.0);
  1710.         Iptr = (int *)NewPtr(buflen * sizeof(int) );
  1711.         /* zero out the buffers */
  1712.         for (i = 0; i < buflen; i++ ) *(buf+i) = 0.0;
  1713.         for (i = 0; i < buflen; i++ ) *(Iptr+i) = 0.0;
  1714.         myPBlkPtr->ioParam.ioBuffer = (Ptr)Iptr;
  1715.         *StartSamp = (long)*SampPtr;
  1716.         *EndSamp = *StartSamp + buflen;
  1717.         *bptr -= buflen;
  1718.         myPBlkPtr->ioParam.ioPosOffset = (long)(*SampPtr*sizeof(int));
  1719.         myPBlkPtr->ioParam.ioReqCount = (long)(buflen*sizeof(int));
  1720.         theErr = PBRead(myPBlkPtr, FALSE);
  1721.         if ( theErr != noErr ) {
  1722.             if ( theErr == eofErr ) {
  1723.                 if (myPBlkPtr->ioParam.ioActCount == 0L ) {
  1724.                     DisposPtr((Ptr)Iptr);
  1725.                     *SampPtr = (double)*EndSamp;
  1726.                     *StartSamp = *EndSamp;
  1727.                     *SampPtr += si;
  1728.                     *bptr += si;
  1729.                     return(0.0);
  1730.                 }
  1731.                 *EndSamp = *StartSamp +
  1732.                     (myPBlkPtr->ioParam.ioActCount / sizeof(int));
  1733.             }
  1734.             if ( myPBlkPtr->ioParam.ioPosOffset < NIL || theErr == eofErr || theErr == posErr )
  1735. /*            mark is outside file bounds (= %ld\n", myPBlkPtr->ioParam.ioPosOffset;*/
  1736.                 ;
  1737.             DisposPtr((Ptr)Iptr);
  1738.         }
  1739.         /* otherwise */
  1740.         nBytes = myPBlkPtr->ioParam.ioActCount;
  1741.         nSamps = nBytes / sizeof(int);
  1742.         for ( i = 0; i < nSamps; i++ )
  1743.             *(buf+i) = (double)*(Iptr+i);
  1744.         DisposPtr((Ptr)Iptr);
  1745.     }
  1746.  
  1747.  
  1748.  
  1749.  
  1750.     /* now check for interpolation */
  1751.     i = (int)*bptr;
  1752.     frac = *bptr - i;
  1753.     *SampPtr += si;
  1754.     *bptr += si;
  1755.     if ( frac == 0.0) {
  1756.         return(*(buf+i) );
  1757.     }
  1758.     k = i + 1;
  1759.     /* check if sample k is in this record */
  1760.     thisSamp = *(buf+i);
  1761.     if ( k >= buflen ) {
  1762.         if ( si < 0.0 ) {
  1763.             /* we must have a negative, fractional sample increment, we have probably
  1764.             just read a new record and must now interpolate between th last sample in
  1765.             this rec and the first sample in the one we just discarded.  To save hassle,
  1766.             just read that sample in, do the interpolation and forget it! */
  1767.             PtrToOldSamp = &oldSamp;
  1768.             myPBlkPtr->ioParam.ioBuffer = (Ptr)PtrToOldSamp;
  1769.             myPBlkPtr->ioParam.ioPosOffset = (long)((*SampPtr+1.0)*sizeof(int));
  1770.             myPBlkPtr->ioParam.ioReqCount = (long)sizeof(int);
  1771.             theErr = PBRead(myPBlkPtr, FALSE);
  1772.             if ( theErr == noErr ) {
  1773.                 return( (double)(thisSamp + ( (oldSamp - thisSamp) * frac ) ));
  1774.             }
  1775.             /* problem reading the sample, just return the the current sample */
  1776.             return(thisSamp);
  1777.         }
  1778.         k = 0;
  1779.         Iptr = (int *)NewPtr(buflen * sizeof(int) );
  1780.         for (i = 0; i < buflen; i++ ) *(buf+i) = 0.0;
  1781.         for (i = 0; i < buflen; i++ ) *(Iptr+i) = 0.0;
  1782.         myPBlkPtr->ioParam.ioBuffer = (Ptr)Iptr;
  1783.         *StartSamp = (long)*SampPtr;
  1784.         *EndSamp = *StartSamp + buflen;
  1785.         myPBlkPtr->ioParam.ioPosOffset = (long)(*SampPtr*sizeof(int));
  1786.         myPBlkPtr->ioParam.ioReqCount = (long)(buflen*sizeof(int));
  1787.         theErr = PBRead(myPBlkPtr, FALSE);
  1788.         if ( theErr != noErr ) {
  1789.             if ( theErr == eofErr ) {
  1790.                 if (myPBlkPtr->ioParam.ioActCount == 0L ) {
  1791.                     DisposPtr((Ptr)Iptr);
  1792.                     *SampPtr = (double)*EndSamp;
  1793.                     *StartSamp = *EndSamp;
  1794.                     *SampPtr += si;
  1795.                     *bptr += si;
  1796.                     return(0.0);
  1797.                 }
  1798.                 *EndSamp = *StartSamp +
  1799.                     (myPBlkPtr->ioParam.ioActCount / sizeof(int));
  1800.             }
  1801.             else {
  1802.                 DisposPtr((Ptr)Iptr);
  1803.                 return(0.0);
  1804.             }
  1805.             if ( myPBlkPtr->ioParam.ioPosOffset < NIL || theErr == eofErr || theErr == posErr )
  1806.                 ;
  1807.             DisposPtr((Ptr)Iptr);
  1808.             return(0.0);
  1809.         }
  1810.         nBytes = myPBlkPtr->ioParam.ioActCount;
  1811.         nSamps = nBytes / sizeof(int);
  1812.         for ( i = 0; i < nSamps; i++ )
  1813.             *(buf+i) = (double)*(Iptr+i);
  1814.         DisposPtr((Ptr)Iptr);
  1815.         *bptr -= buflen;
  1816.     }
  1817.     return( (double)(thisSamp + ( (*(buf+k) - thisSamp) * frac ) ));
  1818. }
  1819.  
  1820.  
  1821.  
  1822.  
  1823. /*****************************************************************/
  1824. Boolean SF_SD_2_ReadSet(buf, buflen, bptr, myPBlkPtr, SampPtr, StartSamp, EndSamp)
  1825.     double    *buf;
  1826.     int        buflen;
  1827.     double    *bptr, *SampPtr;
  1828.     long    *StartSamp, *EndSamp;
  1829.     ParmBlkPtr        myPBlkPtr;
  1830. {
  1831.  
  1832. /* set file pos and  get the buffer full*/
  1833.     register    i;
  1834.     long    nBytes;
  1835.     int    *iptr1, *iptr2;
  1836.     double    *dptr;
  1837.     long    nSamps;
  1838.     long    theLastSamp;
  1839.     long    nrecs;
  1840.     WaveRec    Header;
  1841.     WavPtr    HeaderPtr;
  1842.     
  1843.     iptr1 = (int *)NewPtr(buflen * sizeof(int) );
  1844.     if ( iptr1 == NIL ) {
  1845.         PstringCopy((char *)theMess1, "\pNot enough memory in SF_SD_ReadSet");
  1846.         OSError(theMess1, NIL, theErr);
  1847.     }
  1848.     for (i = 0, dptr = buf, iptr2 = iptr1; i < buflen; i++ ) {
  1849.         *dptr++ = 0.0;
  1850.         *iptr2++ = 0;
  1851.     }
  1852.  
  1853. /* StartSamp points to the actual sample number */
  1854.     myPBlkPtr->ioParam.ioPosMode = fsFromStart;
  1855.     myPBlkPtr->ioParam.ioCompletion = NIL;
  1856. /* we round off to a buffer boundary */
  1857.     myPBlkPtr->ioParam.ioPosOffset = (long)(*StartSamp * sizeof(int));
  1858.     myPBlkPtr->ioParam.ioBuffer = (Ptr)iptr1;
  1859.     myPBlkPtr->ioParam.ioReqCount = (long)(buflen*sizeof(int));
  1860.     *SampPtr = (double)*StartSamp;
  1861.     *EndSamp = *StartSamp + buflen;
  1862.     *bptr = 0.0;
  1863.     theErr = PBRead(myPBlkPtr, FALSE);
  1864.     if (theErr != noErr ) {
  1865.         if ( theErr == eofErr ) {
  1866.         /* round off to a record boundary and read the
  1867.             remaining portion of the file into the buffer */
  1868.             myPBlkPtr->ioParam.ioCompletion = NIL;
  1869.             theErr = PBGetEOF(myPBlkPtr, FALSE);
  1870.             theLastSamp = (long)myPBlkPtr->ioParam.ioMisc / sizeof(int);
  1871.             nrecs = (long)theLastSamp / buflen;
  1872.             *StartSamp = nrecs * buflen;
  1873.             myPBlkPtr->ioParam.ioPosMode = fsFromStart;
  1874.             myPBlkPtr->ioParam.ioCompletion = NIL;
  1875.             myPBlkPtr->ioParam.ioPosOffset = (long)(*StartSamp * sizeof(int));
  1876.             myPBlkPtr->ioParam.ioReqCount = (theLastSamp - *StartSamp) * sizeof(int);
  1877.             theErr = PBRead(myPBlkPtr, FALSE);
  1878.             *EndSamp = theLastSamp;
  1879.             *bptr = (*EndSamp - *StartSamp) - 1;
  1880.             *SampPtr = (double)*EndSamp-1;
  1881.         }
  1882.         else {
  1883.             PstringCopy((char *)theMess1, "\pError reading from the soundfile");
  1884.             OSError(theMess1, NIL, theErr);
  1885.         }
  1886.     }
  1887.     else {
  1888.         *bptr = 0.0;
  1889.         *EndSamp = *StartSamp + buflen;
  1890.     }
  1891.     
  1892.     nBytes = myPBlkPtr->ioParam.ioActCount;
  1893.     nSamps = nBytes / sizeof(int);
  1894.     for ( i = 0, dptr = buf, iptr2 = iptr1; i < nSamps; i++ )
  1895.         *dptr++ = (double)*iptr1++;
  1896.     DisposPtr((Ptr)iptr1);
  1897.     DisposPtr((Ptr)iptr2);
  1898.     DisposPtr((Ptr)dptr);
  1899.     return(TRUE);
  1900. }
  1901.  
  1902.  
  1903.  
  1904.  
  1905. double    SF_SD_2_Read(myPBlkPtr, si, buf, buflen, bptr, SampPtr, StartSamp, EndSamp)
  1906.     ParmBlkPtr        myPBlkPtr;
  1907.     int                buflen;
  1908.     double            si;
  1909.     double             *bptr;        /* points to a sample no WITHIN the buffer */
  1910.     double            *buf;
  1911.     long            *StartSamp, *EndSamp;
  1912.     double            *SampPtr;
  1913. {
  1914. /*
  1915. * interpolating soundfile read of Digidesign's Sound Designer II¬ format files
  1916. * negative and fractional sample increments are accommodated. 
  1917. */
  1918.     register  i;
  1919.     register  k;
  1920.     register    double    frac;
  1921.     register    int    thisSamp;
  1922.     int    oldSamp, *PtrToOldSamp;
  1923.     long    nBytes;
  1924.     int    *Iptr;
  1925.     long    nSamps;
  1926.  
  1927.  
  1928.     if ( *SampPtr < (double)*StartSamp ) {    /* read previous buffer */
  1929.         if ( *SampPtr < 0L )
  1930.             return(0.0);
  1931.         Iptr = (int *)NewPtr(buflen * sizeof(int) );
  1932.         /* zero out the buffers */
  1933.         for (i = 0; i < buflen; i++ ) *(buf+i) = 0.0;
  1934.         for (i = 0; i < buflen; i++ ) *(Iptr+i) = 0.0;
  1935.         myPBlkPtr->ioParam.ioBuffer = (Ptr)Iptr;
  1936.         
  1937.         *EndSamp = *StartSamp;
  1938.         *StartSamp = *EndSamp - buflen;
  1939.         *bptr += buflen;
  1940.         if ( *StartSamp < 0L ) {
  1941.             *StartSamp = 0L;
  1942.             myPBlkPtr->ioParam.ioReqCount =
  1943.                 (long) ((*EndSamp - *StartSamp) * sizeof(int));
  1944.         }
  1945.         else {
  1946.             myPBlkPtr->ioParam.ioReqCount = (long)(buflen*sizeof(int));
  1947.         }
  1948.         
  1949.         
  1950.         myPBlkPtr->ioParam.ioPosOffset = (long)(*StartSamp*sizeof(int));
  1951.         theErr = PBRead(myPBlkPtr, FALSE);
  1952.         if ( theErr != noErr ) {
  1953.             if ( myPBlkPtr->ioParam.ioPosOffset < NIL || theErr == eofErr || theErr == posErr )
  1954. /*            mark is outside file bounds (= %ld\n", myPBlkPtr->ioParam.ioPosOffset;*/
  1955.                 ;
  1956.             *SampPtr += si;
  1957.             *bptr += si;
  1958.             return(0.0);
  1959.         }
  1960.         /* otherwise */
  1961.         nBytes = myPBlkPtr->ioParam.ioActCount;
  1962.         nSamps = nBytes / sizeof(int);
  1963.         for ( i = 0; i < nSamps; i++ )
  1964.             *(buf+i) = (double)*(Iptr+i);
  1965.         DisposPtr((Ptr)Iptr);
  1966.     }
  1967.     else if ( *SampPtr >= (double)*EndSamp ) {    /* read next bufferful */
  1968.         if ( *StartSamp >= *EndSamp )    /* must have already read past EOF */
  1969.             return(0.0);
  1970.         Iptr = (int *)NewPtr(buflen * sizeof(int) );
  1971.         /* zero out the buffers */
  1972.         for (i = 0; i < buflen; i++ ) *(buf+i) = 0.0;
  1973.         for (i = 0; i < buflen; i++ ) *(Iptr+i) = 0.0;
  1974.         myPBlkPtr->ioParam.ioBuffer = (Ptr)Iptr;
  1975.         *StartSamp = (long)*SampPtr;
  1976.         *EndSamp = *StartSamp + buflen;
  1977.         *bptr -= buflen;
  1978.         myPBlkPtr->ioParam.ioPosOffset = (long)(*SampPtr*sizeof(int));
  1979.         myPBlkPtr->ioParam.ioReqCount = (long)(buflen*sizeof(int));
  1980.         theErr = PBRead(myPBlkPtr, FALSE);
  1981.         if ( theErr != noErr ) {
  1982.             if ( theErr == eofErr ) {
  1983.                 if (myPBlkPtr->ioParam.ioActCount == 0L ) {
  1984.                     DisposPtr((Ptr)Iptr);
  1985.                     *SampPtr = (double)*EndSamp;
  1986.                     *StartSamp = *EndSamp;
  1987.                     *SampPtr += si;
  1988.                     *bptr += si;
  1989.                     return(0.0);
  1990.                 }
  1991.                 *EndSamp = *StartSamp +
  1992.                     (myPBlkPtr->ioParam.ioActCount / sizeof(int));
  1993.             }
  1994.             if ( myPBlkPtr->ioParam.ioPosOffset < NIL || theErr == eofErr || theErr == posErr )
  1995. /*            mark is outside file bounds (= %ld\n", myPBlkPtr->ioParam.ioPosOffset;*/
  1996.                 ;
  1997.             DisposPtr((Ptr)Iptr);
  1998.         }
  1999.         /* otherwise */
  2000.         nBytes = myPBlkPtr->ioParam.ioActCount;
  2001.         nSamps = nBytes / sizeof(int);
  2002.         for ( i = 0; i < nSamps; i++ )
  2003.             *(buf+i) = (double)*(Iptr+i);
  2004.         DisposPtr((Ptr)Iptr);
  2005.     }
  2006.  
  2007.  
  2008.  
  2009.  
  2010.     /* now check for interpolation */
  2011.     i = (int)*bptr;
  2012.     frac = *bptr - i;
  2013.     *SampPtr += si;
  2014.     *bptr += si;
  2015.     if ( frac == 0.0) {
  2016.         return(*(buf+i) );
  2017.     }
  2018.     k = i + 1;
  2019.     /* check if sample k is in this record */
  2020.     thisSamp = *(buf+i);
  2021.     if ( k >= buflen ) {
  2022.         if ( si < 0.0 ) {
  2023.             /* we must have a negative, fractional sample increment, we have probably
  2024.             just read a new record and must now interpolate between th last sample in
  2025.             this rec and the first sample in the one we just discarded.  To save hassle,
  2026.             just read that sample in, do the interpolation and forget it! */
  2027.             PtrToOldSamp = &oldSamp;
  2028.             myPBlkPtr->ioParam.ioBuffer = (Ptr)PtrToOldSamp;
  2029.             myPBlkPtr->ioParam.ioPosOffset = (long)((*SampPtr+1.0)*sizeof(int));
  2030.             myPBlkPtr->ioParam.ioReqCount = (long)sizeof(int);
  2031.             theErr = PBRead(myPBlkPtr, FALSE);
  2032.             if ( theErr == noErr ) {
  2033.                 return( (double)(thisSamp + ( (oldSamp - thisSamp) * frac ) ));
  2034.             }
  2035.             /* problem reading the sample, just return the the current sample */
  2036.             return(thisSamp);
  2037.         }
  2038.         k = 0;
  2039.         Iptr = (int *)NewPtr(buflen * sizeof(int) );
  2040.         for (i = 0; i < buflen; i++ ) *(buf+i) = 0.0;
  2041.         for (i = 0; i < buflen; i++ ) *(Iptr+i) = 0.0;
  2042.         myPBlkPtr->ioParam.ioBuffer = (Ptr)Iptr;
  2043.         *StartSamp = (long)*SampPtr;
  2044.         *EndSamp = *StartSamp + buflen;
  2045.         myPBlkPtr->ioParam.ioPosOffset = (long)(*SampPtr*sizeof(int));
  2046.         myPBlkPtr->ioParam.ioReqCount = (long)(buflen*sizeof(int));
  2047.         theErr = PBRead(myPBlkPtr, FALSE);
  2048.         if ( theErr != noErr ) {
  2049.             if ( theErr == eofErr ) {
  2050.                 if (myPBlkPtr->ioParam.ioActCount == 0L ) {
  2051.                     DisposPtr((Ptr)Iptr);
  2052.                     *SampPtr = (double)*EndSamp;
  2053.                     *StartSamp = *EndSamp;
  2054.                     *SampPtr += si;
  2055.                     *bptr += si;
  2056.                     return(0.0);
  2057.                 }
  2058.                 *EndSamp = *StartSamp +
  2059.                     (myPBlkPtr->ioParam.ioActCount / sizeof(int));
  2060.             }
  2061.             else {
  2062.                 DisposPtr((Ptr)Iptr);
  2063.                 return(0.0);
  2064.             }
  2065.             if ( myPBlkPtr->ioParam.ioPosOffset < NIL || theErr == eofErr || theErr == posErr )
  2066.                 ;
  2067.             DisposPtr((Ptr)Iptr);
  2068.             return(0.0);
  2069.         }
  2070.         nBytes = myPBlkPtr->ioParam.ioActCount;
  2071.         nSamps = nBytes / sizeof(int);
  2072.         for ( i = 0; i < nSamps; i++ )
  2073.             *(buf+i) = (double)*(Iptr+i);
  2074.         DisposPtr((Ptr)Iptr);
  2075.         *bptr -= buflen;
  2076.     }
  2077.     return( (double)(thisSamp + ( (*(buf+k) - thisSamp) * frac ) ));
  2078. }
  2079.